package com.heima.user.service.impl;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.client.wemedia.WemediaUserClient;
import com.heima.common.exception.CustomException;
import com.heima.common.redis.CacheService;
import com.heima.model.common.dtos.ArticleInfoDto;
import com.heima.model.common.dtos.LoginDto;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.dtos.UserRelationDto;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.model.common.pojos.user.ApUser;
import com.heima.model.common.pojos.user.ApUserFan;
import com.heima.model.common.pojos.user.ApUserFollow;
import com.heima.model.common.pojos.wemedia.WmUser;
import com.heima.user.mapper.ApUserFanMapper;
import com.heima.user.mapper.ApUserFollowMapper;
import com.heima.user.mapper.ApUserMapper;
import com.heima.user.service.ApUserService;
import com.heima.utils.common.AppJwtUtil;
import com.heima.utils.common.MD5Utils;
import com.heima.utils.thread.ApThreadLocalUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @author 陈辉
 * @data 2024 14:29
 */
@Service
public class ApUserServiceImpl extends ServiceImpl<ApUserMapper, ApUser> implements ApUserService {
    @Autowired
    private ApUserFanMapper userFanMapper;
    @Autowired
    private ApUserFollowMapper userFollowMapper;
    @Autowired
    private CacheService cacheService;

    @Autowired
    private WemediaUserClient wemediaUserClient;
    @Autowired
    private ApUserFollowMapper apUserFollowMapper;


    /**
     * app用户登陆
     *
     * @param loginDto
     * @return
     */
    @Override
    public ResponseResult login(LoginDto loginDto) {
        //1. 判断是游客登陆还是正常登陆
        if (loginDto == null || (StringUtils.isEmpty(loginDto.getPhone())
                && StringUtils.isEmpty(loginDto.getPassword()))) {
            //3. 游客登陆：基于0号用户id生成token返回即可
            String token = AppJwtUtil.getToken(0L);

            Map<String,Object> resData = new HashMap<>();
            resData.put("token",token);
            return ResponseResult.okResult(resData);
        } else {
            //2. 正常登陆
            //2.1 校验手机号
            ApUser user = getOne(Wrappers.<ApUser>lambdaQuery().eq(ApUser::getPhone, loginDto.getPhone()));
            if (user == null)
                throw new CustomException(AppHttpCodeEnum.AP_USER_DATA_NOT_EXIST);

            //2.1 校验密码   -- 加密加盐校验
            //先将前端传递的明文加盐，加盐后再加密，得到密文
            String pwdInput = MD5Utils.encode(loginDto.getPassword() + user.getSalt());
            //将计算得到的密文与数据库中的密码比较
            if (!pwdInput.equals(user.getPassword())){
                throw new CustomException(AppHttpCodeEnum.LOGIN_PASSWORD_ERROR);
            }

            //2.2 校验当前用户状态
            if (user.getStatus() == 1){
                throw new CustomException(AppHttpCodeEnum.LOGIN_STATUS_ERROR);
            }

            //2.3 基于当前用户id生成token令牌
            String token = AppJwtUtil.getToken(Long.valueOf(user.getId()));

            //2.4 将当前用户信息和token令牌都返回即可
            Map<String,Object> resData = new HashMap<>();
            resData.put("token",token);
            resData.put("user",user);

            return ResponseResult.okResult(resData);
        }
    }

    /**
     * 用户取消或者关注
     *
     * @param userRelationDto
     * @return
     */
    @Override
    public ResponseResult userFollow(UserRelationDto userRelationDto) {
        //参数校验
        if (userRelationDto == null || userRelationDto.getArticleId() == null
                || userRelationDto.getAuthorId() == null) {
            throw new CustomException(AppHttpCodeEnum.PARAM_INVALID);
        }
        //获取用户id
        Integer userId = ApThreadLocalUtil.get();
        if (userId == null) {
            throw new CustomException(AppHttpCodeEnum.AP_USER_DATA_NOT_EXIST);
        }
        //查询当前用户的名称
        ApUser user = getOne(Wrappers.<ApUser>lambdaQuery().eq(ApUser::getId, userId));
        if (user == null) {
            throw new CustomException(AppHttpCodeEnum.AP_USER_DATA_NOT_EXIST);
        }
        //查询作者昵称
        ResponseResult response = wemediaUserClient.getWemediaUser(userRelationDto.getAuthorId().toString());
        WmUser wmUser = JSON.parseObject(JSON.toJSONString(response.getData()), WmUser.class);
        if (wmUser == null){
            throw new CustomException(AppHttpCodeEnum.SERVER_ERROR);
        }
        if (userRelationDto.getOperation() == 0) {
            //判断用户是否关注过了改作者
            ApUserFollow userFollow = apUserFollowMapper.selectOne(Wrappers.<ApUserFollow>lambdaQuery()
                    .eq(ApUserFollow::getUserId, userId)
                    .eq(ApUserFollow::getFollowId, userRelationDto.getAuthorId()));
            if (userFollow != null){
                throw new CustomException(AppHttpCodeEnum.FOLLOW_FAIL);
            }
            //关注
            //添加数据库ap_user_fan信息
            ApUserFan apUserFan = new ApUserFan();
            apUserFan.setUserId(userRelationDto.getAuthorId());
            apUserFan.setFansId(userId);
            apUserFan.setFansName(user.getName());
            apUserFan.setCreatedTime(new Date());
            apUserFan.setLevel(0);
            userFanMapper.insert(apUserFan);
            //添加数据库ap_user_follow信息
            ApUserFollow apUserFollow = new ApUserFollow();
            apUserFollow.setUserId(userId);
            apUserFollow.setFollowId(userRelationDto.getAuthorId());
            apUserFollow.setFollowName(wmUser.getNickname());
            apUserFollow.setLevel(0);
            apUserFollow.setIsNotice(null);
            apUserFollow.setCreatedTime(new Date());
            userFollowMapper.insert(apUserFollow);
        } else {
            //取消关注 删除数据
            //删除ap_user_fan表的数据
            //delete * from ap_user_fan where userId = authorId and fansId = userId
            userFanMapper.delete(Wrappers.<ApUserFan>lambdaQuery()
                    .eq(ApUserFan::getUserId, userRelationDto.getAuthorId())
                    .eq(ApUserFan::getFansId, userId));
            //删除ap_user_follow表数据
            //delete * from ap_user_follow where userId = userId and followId = authorId
            userFollowMapper.delete(Wrappers.<ApUserFollow>lambdaQuery()
                    .eq(ApUserFollow::getUserId, userId)
                    .eq(ApUserFollow::getFollowId, userRelationDto.getAuthorId()));
        }
        //存入Redis中
        Map<String, Object> map = new HashMap<>();
        map.put("data", userRelationDto);
        cacheService.hPut("follow_logs:" + userId, userRelationDto.getArticleId().toString(),
                JSON.toJSONString(map));
        return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
    }

    /**
     * 获取用户关注信息
     *
     * @param articleInfoDto@return
     */
    @Override
    public ResponseResult getUserFollow(ArticleInfoDto articleInfoDto) {
        if (articleInfoDto == null || articleInfoDto.getAuthorId() == null){
            throw new CustomException(AppHttpCodeEnum.PARAM_INVALID);
        }
        //查询用户关注信息
        ApUserFollow userFollow = userFollowMapper.selectOne(Wrappers.<ApUserFollow>lambdaQuery()
                .eq(ApUserFollow::getFollowId, articleInfoDto.getAuthorId())
                .eq(ApUserFollow::getUserId, articleInfoDto.getUserId()));
        return ResponseResult.okResult(userFollow);
    }

    /**
     * 查询APP当前登录用户信息
     * @param userId
     * @return
     */
    @Override
    public ResponseResult getUserInfo(Integer userId) {
        if (userId == null) {
            throw new CustomException(AppHttpCodeEnum.PARAM_INVALID);
        }
        ApUser user = getById(userId);
        if (user == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.AP_USER_DATA_NOT_EXIST);
        }
        return ResponseResult.okResult(user);
    }
}
